SoHL - Locus System and calc_ entities

Автор: BUzer


Пожалуй, начну издалека.
Как вы знаете, прежде чем какая-нибудь последовательность триггеров сработает, для этого должно что-нибудь произойти. Список условий довольно широк - кто-то нажал на кнопку, кто-то зашел в некую область, что-то упало на землю, или захлопнулась дверь, да и вообще - мало ли что может послужить причиной. Но большинство этих действий происходят по чьей-то вине - кто-то нажимает на кнопки, ходит по областям, и хлопает дверями. Так вот, locus-ентитей (локусом), в певоначальном понимании этого термина, для некой последовательности триггеров зовется та ентитя, которая вызвала её активацию. Странное, и весьма абстрактное понятие, не правда-ли? Не трудно догадаться, что чаще всего этим самым локусом выступает сам игрок, ведь для большинства триггеров причиной для активации служат именно действия игрока. Но так не всегда - например, для событий, вызываемых trigger_multiplie, локусом может быть и некий монстр, который вошел в его область.
Если вы работали со спиритовыми ентитями, то, наверное, часто замечали поля, помеченные чем-то вроде [LE]. Наличие такой и подобных ей меток в названии поля обозначает, что вместо прямого указания имени ентити вы можете написать здесь ключевое слово "*locus", и это будет служить ссылкой на текущую locus-ентитю. Давайте взглянем на простейший пример:

Имеем кнопку, активирующую env_explosion. В спирите у env_explosion есть новое поле под именем "Initial position [LP]", обозначающее место, где произойдет взрыв. Как показывает нам наличие метки [LP], этим местом может быть и локус. Давайте впишем сюда ключевое слово *locus. Вот и все, теперь можно запускать и смотреть, что получилось. При нажатии игроком этой кнопки, она сообщает триггеру env_explosion, кто ее нажал, и взрыв происходит прямо на месте игрока, где-бы он не стоял. Если дело происходит в мультиплеере, то взорвется, естественно, именно тот игрок, который нажимал кнопку.

Думаю, основную суть вы уловили. К слову, концепция локусов использовалась и в оригинальном half-life - например, в trigger_camera, которая действовала всегда на ее локуса (это можно заметить в мультиплеере). Надо сказать, такая логика камеры в ранних версиях халфы вызывала вылет с ошибкой "Host error..", когда к активации камеры игрок никакого отношения не имел, и она вызывалась с помощью trigger_auto.

Все вышеописанное является только вершиной айсберга, потому что есть еще куча способов использовать locus-систему, кроме как делать ссылку на инициатора событий.

Когда вы активируете какой-то триггер, то вы можете сами указать, какую ентитю он будет использовать в качестве локуса, путем дописывания её имени в скобках сразу после имени триггера. Таким образом, можно слегка доработать наш предыдущий пример - ставим три ентити info_target, и обзываем их как-нибудь по-разному, и вместо одной кнопки ставим три, которые активируют один и тот-же env_explosion, но передают ему разные имена info_target'ов. Получается, что при нажатии разных кнопок взрыв происходит в разных местах. Конечно, для этого и не обязательно было-бы использовать локусы, когда можно просто поставить три разных взрыва, но в качестве примера это вполне сойдет. Этот способ, кстати, довольно сильно напоминает вызов некой функции в компьютерной программе с нужным аргументом.

И наконец, самым полезным в locus-системе является то, что многие триггеры, при активации чего-то, могут передавать при этом некий специальный локус. При этом в названии поля, где запрашивается имя, в конце в скобках написано, что именно будет являться локусом для вызванного события (например, название поля "Fire on collision (locus = shot)" у env_shоoter'а говорит о том, что для триггера, имя которого будет в этом поле, локусом послужит объект, которым выстрелит енв_шутер). Приведем пример использования это штуки:

Имеем env_shooter, env_exsplosion, multi_manager, trigger_relay, и что-либо, активирующее env_shooter (в данном случае, не суть важно). Настравиваем енв_шутер, чтобы он выстреливал любую понравившуюся вам модель в нужном вам направлении (например, модель гранаты или банки из-под кока-колы). Настраиваем env_explosion, чтобы он, как в предыдущих примерах, взрывал локус, ставим флаг "repeatable". В свойствах trigger_relay в поле "kill target" также пишем *locus. Заходим в мультименеджер, и заставляем его через три секунды активировать взрыв и реле одновременно, ставим ему флаг "Multi-threaded", а затем пишем имя этого мульименеджера поле "Fire on spawn (locus = shot)" у env_shooter'а.
В итоге получается такая штука - после того, как шутер выстрелит модель, через три секунды она взорвется, калеча всех в округе, и, соответственно, исченет.


В конце статьи я приложу карту, где будет показано, как сделать управляемую пушку, стреляющую такими-же взрывающимися банками (env_shooter тут тоже замешан )

В итоге, способ примерения Locus-системы и её возможностей зависит, в основном, от ентитей, которые вы используете, а точнее, насколько в этих ентитях это предусмотрено. Теперь, после получения представлений об этой системе, давайте постепенно переходить к "калькам" - calc_ентитям. Но для начала разберем, чем отличаются метки [LE], [LP], [LV], и [LR].


В первую очередь, метки указывают, как будут использоваться те данные, которые вы задаете. Во всех полях, помеченных таким образом, как правило, пишется имя какой-нибудь ентити, а метка обозначает, какое её свойство будет использовано триггером.




Уфх, вот, вроде, со всеми метками и закончили, теперь наконец-то приступим к этим калькам, о которых я так долго трындел


calc_ентити нужны для того, чтобы модифицировать передаваемые триггерам значения свойств position, vector, и ratio. Используются они таким образом: в полях, помеченных [LP], [LV], или [LR] вы пишете имя соответствующей этому типу данных calc_ентити, в свойствах которой уже задаете, как именно будет расчитываться значение. Ну давайте по порядку:


Ну вот и всё пока что! Наверное, в следующий раз напишу про что-нибудь, вроде спиритового мультименеджера
Надеюсь, эта статья дала вам пищчу для размышлений о том, как вопротить ваши идеи! А вот и обещанная карта - там пушка, стреляющая банками, супер-дверь (), управляемая машинка (правда она сквозь стены ездиет, и приборная панель месте с ней не вращается, но зато она хорошо демонстрирует ипользование ratio и калек), и бонус - дымящийся func_pushable Запускать, естественно, под спирит

PS: если что, простите за опечатки и огрехи, просто поздновато тут уже

вот карта: http://buzer2001.pisem.net/demo.zip



Разделы